package com.haoyun.mirage.user.controller;


import com.baomidou.mybatisplus.plugins.Page;
import com.google.common.collect.Sets;
import com.haoyun.common.controller.BaseController;
import com.haoyun.common.controller.UserInfo;
import com.haoyun.common.core.Result;
import com.haoyun.common.utils.Query;
import com.haoyun.mirage.user.common.enums.UserLevelEnum;
import com.haoyun.mirage.user.model.dto.RoleDTO;
import com.haoyun.mirage.user.model.dto.UserDTO;
import com.haoyun.mirage.user.model.entity.SysUser;
import com.haoyun.mirage.user.model.vo.MenuTree;
import com.haoyun.mirage.user.model.vo.RoleVO;
import com.haoyun.mirage.user.model.vo.UserVO;
import com.haoyun.mirage.user.service.ISysMenuService;
import com.haoyun.mirage.user.service.ISysUserService;
import com.xiaoleilu.hutool.bean.BeanUtil;
import com.xiaoleilu.hutool.collection.CollectionUtil;
import com.xiaoleilu.hutool.util.RandomUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.validation.BindingResult;
import org.springframework.validation.FieldError;
import org.springframework.web.bind.annotation.*;

import javax.validation.Valid;
import java.util.List;
import java.util.Map;
import java.util.Set;

/**
 * <p>
 * 用户表 前端控制器
 * </p>
 *
 * @author twg
 * @since 2018-05-30
 */
@Slf4j
@RestController
@RequestMapping("/user")
public class SysUserController extends BaseController {

    @Autowired
    private ISysUserService userService;
    @Autowired
    private ISysMenuService menuService;

    /**
     * 通过ID查询当前用户信息
     *
     * @param id ID
     * @return 用户信息
     */
    @GetMapping("/{id}")
    public UserDTO user(@PathVariable Long id) {
        return userService.getUserWithRoleDeptById(id);
    }

    /**
     * 获取当前用户信息（角色、权限）
     * 并且异步初始化用户部门信息
     *
     * @return 用户名
     */
    @GetMapping("userInfo")
    public Result<UserVO> userInfo() {
        UserVO userVO = getUserRolesByName(currentUser().getUserName());
        userVO.setPermissions(menuService.findPermission(userVO.getRoles()));
        //用户密码进行保护
        userVO.setUserPassword("");
        return Result.buildSuccessResult(userVO);
    }

    /**
     * 用户添加
     *
     * @param user
     * @param bindingResult
     * @return
     */
    @PostMapping("add")
    public Result<String> addUser(@RequestBody @Valid UserVO user, BindingResult bindingResult) {
        List<FieldError> fieldErrors = bindingResult.getFieldErrors();
        for (FieldError fieldError : fieldErrors) {
            return Result.buildErrorResult(fieldError.getDefaultMessage());
        }
        String salt = RandomUtil.randomString(10);
        String pass = new BCryptPasswordEncoder().encode(user.getUserPassword() + salt);

        UserDTO userDTO = new UserDTO();
        BeanUtil.copyProperties(user, userDTO);
        userDTO.setSalt(salt);
        userDTO.setUserPassword(pass);
        userService.insertUser(userDTO);
        return Result.buildSuccessResult("添加成功");
    }

    /**
     * 更新用户信息
     *
     * @param user 用户信息
     */
    @PutMapping
    public Result<String> userUpdate(@RequestBody @Valid UserVO user, BindingResult bindingResult) {
        List<FieldError> fieldErrors = bindingResult.getFieldErrors();
        for (FieldError fieldError : fieldErrors) {
            return Result.buildErrorResult(fieldError.getDefaultMessage());
        }
        UserDTO userDTO = new UserDTO();
        BeanUtil.copyProperties(user, userDTO);
        userService.updateUser(userDTO);
        return Result.buildSuccessResult("更新成功");
    }


    /**
     * 分页查询用户
     *
     * @param params 参数集
     * @return 用户集合
     */
    @GetMapping("/userPage")
    public Page userPage(Map<String, Object> params) {
        UserInfo userInfo = currentUser();
        if (!UserLevelEnum.SUPER_ADMIN_LEVEL.getLevel().equals(userInfo.getUserLevel())) {
            params.put("compId", userInfo.getCompId());
        }
        if (UserLevelEnum.SUPER_ADMIN_LEVEL.getLevel().equals(userInfo.getUserLevel()) ||
                UserLevelEnum.ADMIN_LEVEL.equals(userInfo.getUserLevel())) {
            params.put("creator", userInfo.getId());
        }
        return userService.findUserByPage(new Query(params));
    }

    /**
     * 通过用户名获取用户信息
     *
     * @param username
     * @return
     */
    @GetMapping("getUserByName/{username}")
    public UserVO getUserByName(@PathVariable("username") String username) {
        UserDTO user = userService.getUserByName(username);
        UserVO userVO = new UserVO();
        BeanUtil.copyProperties(user, userVO);
        return userVO;
    }

    /**
     * 通过用户名获取用户、角色信息
     *
     * @param username
     * @return
     */
    @GetMapping("getUserRolesByName/{username}")
    public UserVO getUserRolesByName(@PathVariable("username") String username) {
        UserDTO userDTO = userService.getUserWithRoleByName(username);
        UserVO user = new UserVO();
        if (null == userDTO){
            return user;
        }
        BeanUtil.copyProperties(userDTO, user);
        List<RoleDTO> roleDTOS = userDTO.getRoles();
        if (CollectionUtil.isEmpty(roleDTOS)) {
            return user;
        }
        RoleVO role = null;
        Set<RoleVO> roles = Sets.newHashSet();
        for (RoleDTO roleDTO : roleDTOS) {
            role = new RoleVO();
            role.setRoleCode(roleDTO.getRoleCode());
            role.setRoleName(roleDTO.getRoleName());
            roles.add(role);
        }
        user.setRolesSet(roles);
        return user;
    }

    /**
     * 删除用户
     *
     * @param id
     * @return
     */
    @DeleteMapping("/{id}")
    public Result<String> deleteUser(@PathVariable("id") Long id) {
        if (id.equals(currentUser().getId())) {
            return Result.buildErrorResult("该用户所属本人，不能删除");
        }
        SysUser user = userService.selectById(id);
        if (user == null) {
            return Result.buildErrorResult("该用户不存在");
        }
        userService.deleteUserById(id);
        return Result.buildSuccessResult("删除成功");
    }


    /**
     * 返回当前用户的树形菜单集合
     *
     * @return 当前用户的树形菜单
     */
    @GetMapping(value = "/userTree")
    public List<MenuTree> userTree() {
        return menuService.findMenuTreeByRoleCodes(findRoles().toArray(new String[]{}));
    }
}

